import { Exclude } from 'class-transformer'; // Exclude 该装饰器作用为查询该字段时不返回该字段，如密码
import {
  BeforeInsert,
  Column,
  Entity,
  OneToMany,
  PrimaryGeneratedColumn,
} from 'typeorm'; // typeorm ORM技术（Object-Relational Mapping），把关系数据库的变结构映射到对象上
// 加密插件
import * as bcrypt from 'bcryptjs';
import { ApiProperty } from '@nestjs/swagger';
import { PostsEntity } from 'src/posts/posts.entity';
@Entity('user')
export class User {
  @ApiProperty({ description: '用户id' })
  @PrimaryGeneratedColumn('uuid') // 创建一个独特的主列id
  id: string;

  @Column({ length: 100, nullable: true })
  username: string;

  @Column({ length: 100, nullable: true })
  nickname: string;
 
  @Column({ length: 11, nullable: true })
  phone: string;

  @Column({ length: 20, nullable: true })
  email: string;

  @Column({ length: 100, nullable: true })
  remark: string;

  @Exclude() // 忽略保存时返回的字段
  @Column({ select: false, nullable: true }) // select 就行查询时是否隐藏此列，但是使用保存的save方法仍然会返回此字段
  password: string;

  @Column({ default: null })
  avatar: string;

  @Column({ default: null })
  openid: string;

  @Column('enum', { enum: ['root', 'author', 'visitor'], default: 'visitor' }) // 三个角色 root有所以权限，author有写文章权限，visitor只能阅读文章， 注册的用户默认是visitor,root权限的账号可以修改用户角色
  role: string;

  @OneToMany(() => PostsEntity, (post) => post.author)
  posts: PostsEntity[];

  @Column({
    name: 'create_time',
    type: 'timestamp',
    default: () => 'CURRENT_TIMESTAMP',
  })
  createTime: Date;

  @Exclude()
  @Column({
    name: 'update_time',
    type: 'timestamp',
    default: () => 'CURRENT_TIMESTAMP',
  })
  updateTime: Date;

  @BeforeInsert() //装饰器@BeforeInsert来装饰encryptPwd方法，表示该方法在数据插入之前调用，这样就能保证插入数据库的密码都是加密后的
  async encryptPwd() {
    if (!this.password) return;
    /**
     * 加密处理
     * bcrypt.hashSync(data, 10)
     * --data 要加密的数据
     * --slat 用于哈希密码的盐，如果指定为数字，则将使用指定的轮数生成盐并将其使用，推荐10
     */
    this.password = await bcrypt.hashSync(this.password, 10);
  }
}
